package com.bmft.task01.dao.impl;

import com.bmft.task01.dao.AnimalDao;
import com.bmft.task01.data.AnimaMapData;

import java.util.Map;

/**
 * @author Jarvan
 * @version 1.0
 * @create 2020/9/26 10:48
 */
public class AnimalDaoImpl implements AnimalDao {
    /**
     * Here is the meaning of this
     * <Animal name,<speciality name, speciality>>
     */
    private static Map<String, Map<String, Object>> map = AnimaMapData.getMap();

    /**
     * Insert a new Animal
     *
     * @param animalName animal name
     * @param animal     animal
     * @return whether insert success.
     */
    @Override
    public boolean insertAnimal(String animalName, Map<String, Object> animal) {
        Map<String, Object> put = map.put(animalName, animal);
        return put != null;
    }

    /**
     * Delete a Animal
     *
     * @param animalName
     * @return whether delete success.
     */
    @Override
    public boolean deleteAnimal(String animalName) {
        Map<String, Object> remove = map.remove(animalName);
        return remove != null;
    }

    /**
     * Modify a Animal name
     *
     * @param oldName old name
     * @param newName new name
     * @return whether modify success.
     */
    @Override
    public boolean modifyAnimalName(String oldName, String newName) {
        boolean insertAnimal = insertAnimal(newName, queryCharacteristics(oldName));
        boolean deleteAnimal = deleteAnimal(oldName);
        return insertAnimal && deleteAnimal;
    }

    /**
     * Get all the animal.
     *
     * @return all the animal
     */
    @Override
    public Map<String, Map<String, Object>> queryAllAnimalList() {
        return AnimaMapData.getMap();
    }

    /**
     * Insert Animal characteristic .
     *
     * @param animalName         animal name
     * @param characteristicName animal characteristic name.
     * @param characteristic     characteristic
     * @return whether insert success or not.
     */
    @Override
    public boolean insertCharacteristic(String animalName, String characteristicName, Object characteristic) {
        if (existAnimal(animalName)) {
            return map.get(animalName).put(characteristicName, characteristic) != null;
        }
        return false;
    }

    /**
     * Delete characteristic of  the animal.
     *
     * @param animalName         animal name.
     * @param characteristicName characteristic name.
     * @return whether delete success or not.
     */
    @Override
    public boolean deleteCharacteristic(String animalName, String characteristicName) {
        if (existAnimal(animalName)) {
            return map.get(animalName).remove(characteristicName) != null;
        }
        return false;
    }

    /**
     * Update characteristic fo the animal.
     *
     * @param animalName         animal name
     * @param characteristicName characteristic name
     * @param newCharacteristic  new characteristic
     * @return where update success or not.
     */
    @Override
    public boolean updateCharacteristic(String animalName, String characteristicName, Object newCharacteristic) {
        if (existAnimal(animalName)) {
            Map<String, Object> animal = map.get(animalName);
            return animal.replace(characteristicName, newCharacteristic) != null;
        }
        return false;
    }

    /**
     * query all the characteristics of the animal.
     *
     * @param animalName animal name.
     * @return animal include it's characteristics.
     */
    @Override
    public Map<String, Object> queryCharacteristics(String animalName) {
        return map.get(animalName);
    }

    /**
     * Whether animal exist.
     *
     * @param animalName animal name.
     * @return true if animal exist.
     */
    @Override
    public boolean existAnimal(String animalName) {
        return map.get(animalName) != null;
    }

    /**
     * Update animal name.
     *
     * @param animalOldName animal old name.
     * @param animalNewName animal new name.
     * @return true if name update success.
     */
    @Override
    public boolean updateAnimalName(String animalOldName, String animalNewName) {
        if (existAnimal(animalOldName)){
            Map<String, Object> old = map.get(animalOldName);
            map.put(animalNewName,old);
            map.remove(animalOldName);
            return true;
        }
        return false;
    }
}
